home *** CD-ROM | disk | FTP | other *** search
/ The 640 MEG Shareware Studio 2 / The 640 Meg Shareware Studio CD-ROM Volume II (Data Express)(1993).ISO / prog / rexxpc_2.zip / REXXPC-3.DOC < prev   
Text File  |  1988-03-16  |  62KB  |  2,234 lines

  1.     THE PARSE INSTRUCTION
  2.  
  3.  
  4.  
  5. The parse instruction allows a string to be "dissected" into sub-fields
  6. under control of a list of scanning specifiers and variable names.
  7.  
  8. The syntax of the instruction is:
  9.  
  10.   statement     ::=  PARSE [ upper ] specification template
  11.  
  12.                      │      SOURCE           │
  13.   specification ::=  │      VERSION          │
  14.                      │ VALUE expression WITH │
  15.                      │ VAR   varname         │
  16.                      │ PULL  expression      │
  17.                      │ ARG   expression      │
  18.                      │ LINEIN  expression    │
  19.  
  20.   template  ::=  [ firstPosition ] assignment
  21.                        [ assignment ]
  22.  
  23.                                      │ varname │
  24.   assignment ::= [ nextPosition ]    │         │
  25.                                      │   dot   │
  26.                         [ stopPosition ]
  27.  
  28.   firstPosition ::=  position
  29.  
  30.   nextPosition  ::=  position [ nextPosition ]
  31.  
  32.   stopPosition  ::=  position
  33.  
  34.   position      ::=  │ searchPosition   │
  35.                      │ absolutePosition │
  36.                      │ relativePosition │
  37.                      │ ( varname )      │
  38.  
  39.   searchPosition    ::= ' stringSought '
  40.  
  41.   absolutePosition  ::=  columnNumber
  42.  
  43.                          │+ number│
  44.   relativePosition  ::=  │        │
  45.                          │- number│
  46.  
  47.   varname           ::=  variable containing position or literal info
  48.  
  49.  
  50. SIMPLE TEMPLATE
  51.  
  52.  
  53. 1.  In its simplest form, the template is a list of variable names and
  54.     the source string is assigned to the variables listed in the template
  55.     one word at a time.  (A word is delimited by blanks).  For example,
  56.     the following instruction would assign "one" to "a", "two" to "b",
  57.     and "three" to "c".
  58.  
  59.       parse value 'one two    three' with a b c d
  60.  
  61. 2.  If there are more words in the source string than variable names in
  62.     the template, the remainder of the string is assigned to the last
  63.     variable.  For example, the following instruction would assign "one"
  64.     to "a" and "two three" to "b":
  65.  
  66.       parse value 'one two    three' with a b
  67.  
  68. 3.  If a dot appears in the template instead of a variable name, then the
  69.     word in the source string corresponding to the dot is thrown away.
  70.     For example, the following instruction would assign "one" to "a" and
  71.     "four" to "b":
  72.  
  73.       parse value 'one two     three four'
  74.             with a . . b
  75.  
  76.  
  77. The Parse Instruction                                                  51
  78. TEMPLATE WITH PATTERNS
  79.  
  80.  
  81. 1.  You can specify a  start position in the source string by specifying
  82.     a character pattern.  For example, the following instruction would
  83.     assign "one" to "a" and "two" to "b":
  84.  
  85.       parse value 'a$one two three' with '$' a b .
  86.  
  87. 2.  You can also specify a stop position the same way.  For example, the
  88.     following instruction would assign "one" to "a", "two" to "b", and
  89.     "three" to "c":
  90.  
  91.       parse value 'a:/one/two/three'
  92.             with '/' a '/' b '/' c
  93.  
  94.  
  95.  
  96. TEMPLATE WITH ABSOLUTE COLUMN POSITIONS
  97.  
  98.  
  99. 1.  Instead of character patterns, you can specify absolute column posi-
  100.     tions.  For example, the following instruction would assign "one" to
  101.     "a":
  102.  
  103.       parse value '$$$one$$$two$$$three$$$' with 4 a 7
  104.  
  105. 2.  Multiple start and stop positions may be specified.  For example,, the
  106.     following instruction would assign "one" to "a", "two" to "b", and
  107.     "three" to "c":
  108.  
  109.       parse value '$$$one$$$two$$$three$$$'
  110.             with 4 a 7 10 b 13 16 c 21
  111.  
  112.  
  113.  
  114. TEMPLATE WITH RELATIVE COLUMN POSITIONS
  115.  
  116.  
  117. 1.  A start position may be specified relative to the previous stop po-
  118.     sition.  For example, the following instruction would assign  "two"
  119.     to "a":
  120.  
  121.       parse value 'one two/three' with '/' -3 a '/'
  122.  
  123. 2.  A stop position may be specified the same way.  For example, the
  124.     following instruction would assign "two" to "a":
  125.  
  126.       parse value 'one two/three' with '/' -3 a +3
  127.  
  128.       Note: A major bug, with relative position and literal matches,
  129.       was found during testing.  The rule states that the use
  130.       of a relative positionAFTER a literal search will
  131.       RESET the left edge to the LAST encountered LITERAL
  132.       MATCH and count from there.  If you find that your
  133.       previous programs are failing please check this area
  134.       carefully.  Sorry for the inconvenience but this has been
  135.       corrected.
  136.  
  137.  
  138.  
  139. TEMPLATE WITH VARIABLES AS SPECIFICATIONS
  140.  
  141.  
  142. 1.  A start or stop position may be specified by specifying a variable
  143.     name in parens.  For example, the following instruction would assign
  144.     "three" to "a" (assuming that varname spec contained the value '/'):
  145.  
  146.       parse value 'one two/three' with (spec) a (spec)
  147.  
  148. 2.  A stop position may be specified the same way.  For example, the
  149.     following instruction would assign "two" to "a":
  150.  
  151.       parse value 'one two/three' with (spec) -3 a +3
  152.  
  153.  
  154. The parse Instruction                                                  52
  155. FURTHER EXAMPLES
  156.  
  157.  
  158. For a good description of the parse instruction, the document The REXX
  159. Executor - General Documentation by Mike Cowlishaw is recommended read-
  160. ing.
  161.  
  162.  
  163.  
  164.  
  165.  
  166.  
  167.  
  168.  
  169.  
  170.  
  171.  
  172.  
  173.  
  174.  
  175.  
  176.  
  177.  
  178.  
  179.  
  180.  
  181.  
  182.  
  183.  
  184.  
  185.  
  186.  
  187.  
  188.  
  189.  
  190.  
  191.  
  192.  
  193.  
  194.  
  195.  
  196.  
  197.  
  198.  
  199.  
  200.  
  201.  
  202.  
  203.  
  204.  
  205.  
  206.  
  207.  
  208.  
  209.  
  210.  
  211.  
  212.  
  213.  
  214.  
  215.  
  216.  
  217.  
  218.  
  219.  
  220.  
  221.  
  222.  
  223.  
  224.  
  225.  
  226.  
  227.  
  228.  
  229.  
  230.  
  231. The Parse Instruction                                                  53
  232. APPENDIX A. DEBUGGING
  233.  
  234.  
  235.  
  236. The REXX language includes a mechanism for interactively controlling the
  237. execution of a program.
  238.  
  239. Changing the TRACE setting to one with a prefix "?" (for example, "TRACE
  240. ?ALL", or using the TRACE built-in function) turns on interactive tracing,
  241. and also informs the user that tracing is now interactive.  The language
  242. processor will then ignore further trace instructions in the program, and
  243. will pause after nearly all instructions that are traced.  Once the
  244. processor has paused then the following actions are possible:
  245.  
  246. 1.  Entering a null line (no blanks even) will make the language processor
  247.     continue execution until the next pause for interactive input.  Re-
  248.     peatedly entering a null line will therefore step from pause point
  249.     to pause point.  For "TRACE ?ALL", for example, this is equivalent to
  250.     single stepping through the program.
  251. 2.  Anything else entered will be treated as a string of one or more
  252.     clauses to be interpreted immediately.  They are executed by the same
  253.     mechanism as the INTERPRET instruction, and the same rules apply (for
  254.     example, DO..END constructs must be complete, etc.).  If an instruc-
  255.     tion has a syntax error in it, a standard message will be displayed
  256.     and you will be prompted for input again. - the error will not be
  257.     trapped by SIGNAL ON SYNTAX or cause exit from the program.  Similarly
  258.     all other SIGNAL conditions are disabled while the string is inter-
  259.     preted, to prevent unintentional transfer of control.
  260.  
  261.     Note: Currently for version 0.55 syntax errors WILL cause exit from
  262.     the program.
  263.  
  264.     During interpretation of the string, no tracing takes place, except
  265.     that error return codes from host commands are displayed.  The special
  266.     variable RC is not set by commands executed from the string.
  267.  
  268.     Once the string has been interpreted, the language processor pauses
  269.     again for further interactive input unless a TRACE instruction was
  270.     executed during the interpretation.  In this later case the processor
  271.     will immediately alter the trace setting (if necessary) and then
  272.     continue executing until the next pause point (if any). Hence to alter
  273.     the trace setting (from "ALL" to "Results" for example) and then re-
  274.     execute the instruction, you must use the built-in TRACE function.
  275.     For example,  "CALL TRACE I" will ensure that the trace setting is
  276.     "I" and allow re-execution of the clause after which the pause was
  277.     made.  Interactive tracing will be turned off only if a TRACE in-
  278.     struction uses a "?" prefix (or is "TRACE Off").
  279.  
  280. The trace action selected by a TRACE instruction is saved and restored
  281. across subroutine calls.  This means that if you are stepping through a
  282. program (say after using "TRACE ?Results") then enter a subroutine in
  283. which you have no interest, you can then enter "TRACE Off".  No further
  284. instructions in the subroutine will be traced, but on return to the caller
  285. tracing will be restored.
  286.  
  287. Similarly, if you are only interested in a subroutine, you can put a
  288. "TRACE ?R" instruction at its start.  Having traced the routine, the ori-
  289. ginal status of tracing will be restored and hence, (if tracing was off
  290. on entry to the subroutine) all tracing will be turned off until the next
  291. entry to the subroutine.
  292.  
  293. Since any instructions may be executed during interactive tracing you have
  294. considerable control over execution.
  295.  
  296. Examples:
  297.  
  298. say expr  will display the result of evaluating the expression
  299.  
  300. name=expr will alter the value of the variable name
  301.  
  302. trace off will turn off all tracing
  303.  
  304. trace ?all will turn off interactive tracing but continue tracing all
  305.           clauses.
  306.  
  307.  
  308. Appendix A. Debugging                                                  54
  309. trace L   will make the language processor pause at labels only.  This is
  310.           similar to the traditional "breakpoint" function, except that
  311.           you do not have to know the exact name and spelling of the la-
  312.           bels in the program.
  313.  
  314.           Note: Notice the lack of a "?" in front of the "L", as inter-
  315.           active tracing is already active, it is not necessary.
  316.  
  317. exit      will terminate execution of the program.
  318.  
  319. Do i=1 to 10; say stem.i; end; would display ten elements of the array
  320.           "STEM".
  321.  
  322.  
  323.  
  324.  
  325.  
  326.  
  327.  
  328.  
  329.  
  330.  
  331.  
  332.  
  333.  
  334.  
  335.  
  336.  
  337.  
  338.  
  339.  
  340.  
  341.  
  342.  
  343.  
  344.  
  345.  
  346.  
  347.  
  348.  
  349.  
  350.  
  351.  
  352.  
  353.  
  354.  
  355.  
  356.  
  357.  
  358.  
  359.  
  360.  
  361.  
  362.  
  363.  
  364.  
  365.  
  366.  
  367.  
  368.  
  369.  
  370.  
  371.  
  372.  
  373.  
  374.  
  375.  
  376.  
  377.  
  378.  
  379.  
  380.  
  381.  
  382.  
  383.  
  384.  
  385. Appendix A. Debugging                                                  55
  386. APPENDIX B. SPECIAL FILES
  387.  
  388.  
  389.  
  390. The following filenames are treated specially by REXXPC88:
  391.  
  392. 1.  "screen"
  393.  
  394.     This filename may be used with the seek(), read(), and write() func-
  395.     tions to directly access the contents of the video refresh buffer.
  396.     ∙   seek ('screen', position) sets the reading/writing position on the
  397.         screen and places the cursor there.  The position must be in the
  398.         range 0..1999.  0 corresponds to the upper left corner of the
  399.         screen, 1999 to the lower right.
  400.     ∙   read('screen')  returns  one  linefull  of  characters from the
  401.         screen, starting at the current reading position.  The reading
  402.         position is then advanced to the start of the next line, in
  403.         preparation for another read() or write ().
  404.     ∙   write('screen', text) writes the specified text to the screen at
  405.         the current writing position.  The writing position is then ad-
  406.         vanced by the length of the text, in preparation for another
  407.         write() or read().  The cursor is placed at this new writing po-
  408.         sition.
  409.     ∙   write('screen', text, attribute) writes the text with the indi-
  410.         cated attribute.  The attribute must be a number in the range
  411.         0..255.  For example the following instructions write a blinking
  412.         reverse video HELLO in the middle of the screen:  For more in-
  413.         formation concerning the attribute values see your Personal Com-
  414.         puter Technical Reference under Characters, Keystrokes, and
  415.         Colors.
  416.  
  417.           /* goto center of screen */
  418.           call seek 'screen', (12 * 80) + 40
  419.           /* say HELLO */
  420.           call write 'screen', 'HELLO', 240
  421.  
  422. 2.  "keyboard"
  423.  
  424.     This filename may be used with the read() function to obtain a single
  425.     unechoed keystroke.  The seek(), write(), and size() functions may not
  426.     be used on this file.
  427.  
  428. 3.  "con", "prn", etc.
  429.  
  430.     The DOS filenames for the various input/output devices may be used
  431.     with the read() and write() functions, as appropriate.  The seek()
  432.     and size() function calls may not be used on these files.  Example:
  433.  
  434.       /* write bell to the printer */
  435.       call write 'prn', '07'x
  436.       /* write 'clear' to ansi.sys */
  437.       call write 'con', '1b'x ││ '[2J'
  438.       x = read('con') /* read a line, standard input */
  439.  
  440.  
  441.  
  442.  
  443.  
  444.  
  445.  
  446.  
  447.  
  448.  
  449.  
  450.  
  451.  
  452.  
  453.  
  454.  
  455.  
  456.  
  457.  
  458.  
  459.  
  460.  
  461.  
  462. Appendix B. Special Files                                              56
  463. APPENDIX C. SPECIAL VARIABLES
  464.  
  465.  
  466.  
  467. THE SPECIAL VARIABLE "RESULT"
  468.  
  469.  
  470. The variable named "result" holds the value returned by the routine most
  471. recently invoked by call.  If the routine didn't return any value then
  472. "result" is uninitialized (i.e., its value is equal to its name).
  473.  
  474.  
  475.  
  476. THE SPECIAL VARIABLE "RC"
  477.  
  478.  
  479. The variable rc holds the exit value returned by the most recent external
  480. REXXPC88 program, DOS system command, or user program and may be used to
  481. check for their successful completion.  Some notes on DOS return code
  482. behavior:
  483.  
  484. 1.  Many programs don't supply return codes when they exit (i.e. programs
  485.     returning via int 20H or int 21H, subfunction 0).  REXXPC88 supplies a
  486.     return code of "0" for such programs.
  487. 2.  A positive return code indicates the program was executed and returned
  488.     the indicated value.
  489. 3.  A negative return code indicates the command couldn't be executed.
  490.     Some of the more interesting return codes are:
  491.  
  492.     -2    file not found
  493.  
  494.     -3    path not found
  495.  
  496.     -8    insufficient memory
  497.  
  498.     -15   invalid drive
  499.  
  500.     For a complete summary see your Disk Operating System manual, appendix
  501.     D, section "Error Return Table".
  502.  
  503. 4.  DOS "internal" commands don't supply return codes and REXXPC88  has
  504.     no way of checking for the successful completion of such commands.
  505.     Therefore, the value of "rc" for such commands should be ignored.  The
  506.     following commands are DOS "internal" commands:
  507.  
  508.     a.  BREAK
  509.     b.  CD
  510.     c.  CHDIR
  511.     d.  CLS
  512.     e.  COPY
  513.     f.  CTTY
  514.     g.  DATE
  515.     h.  DEL
  516.     i.  DIR
  517.     j.  ECHO
  518.     k.  ERASE
  519.     l.  MD
  520.     m.  MKDIR
  521.     n.  PATH
  522.     o.  PAUSE
  523.     p.  PROMPT
  524.     q.  RD
  525.     r.  REN
  526.     s.  RENAME
  527.     t.  RMDIR
  528.     u.  SET
  529.     v.  TIME
  530.     w.  TYPE
  531.     x.  VER
  532.     y.  VERIFY
  533.     z.  VOL
  534.  
  535.  
  536.  
  537.  
  538.  
  539. Appendix C. Special variables                                          57
  540. APPENDIX D. INSTALLATION AND USE
  541.  
  542.  
  543. THE CHOICES
  544.  
  545.  
  546. REXXPC88 may be used in two ways:
  547.  
  548. ∙   As a standalone program
  549.  
  550.     With this version you must explicitly precede a command entered at
  551.     the keyboard with the word "REXXIBM" if you wish the command to be
  552.     processed by REXXIBM (i.e. "REXXIBM FOO RED BLUE" will execute the
  553.     batch file named "FOO" with the arguments "RED BLUE").
  554.  
  555. ∙   As a resident extension to DOS
  556.  
  557.     With this version commands typed at the keyboard are resolved ac-
  558.     cording to the following hierarchy:
  559.  
  560.     1.  is it a REXXPC88 batch file program?
  561.     2.  is it a DOS batch file program?
  562.     3.  is it a .COM program?
  563.     4.  is it an .EXE program?
  564.     5.  none of the above? ──> error
  565.  
  566.  
  567.  
  568. WHICH VERSION IS FOR YOU?
  569.  
  570.  
  571. There are advantages and disadvantages to both versions:
  572.  
  573.  
  574.  
  575. Characteristics of Resident Version
  576.  
  577.  
  578. 1.  The resident version consumes approximately 80k of storage.
  579. 2.  User extensions may be added by supplying code at software interrupt
  580.     7CH and watching for subfunction 0005.
  581. 3.  REXXPC88 may be invoked by user programs via software interrupt 7CH
  582.     using subfunctions 0000 and 0001.
  583.  
  584.  
  585.  
  586. Characteristics of Standalone Version
  587.  
  588.  
  589. 1.  No storage is wasted when REXXPC88 programs are not running.
  590. 2.  REXXPC88 programs cannot execute the "PATH" "CTTY" or "SET" commands.
  591. 3.  REXXPC88 extensions may not be used.
  592. 4.  REXXPC88 may be invoked by user programs via DOS function 4B.
  593.  
  594.  
  595.  
  596. * BI-LINGUAL BATCH FILE SUPPORT
  597. *
  598. *
  599. * Starting with release 0.54 Dated June 5, 1987, REXXPC88 provides support
  600. * for bi-lingual batch files. A bi-lingual batch file can be run as a normal
  601. * DOS  batch  file  if REXXIBMR  is  not installed, or as a normal REXXPC88
  602. * program if REXXIBMR is installed.
  603. *
  604. * A normal REXXPC88 program is identified with the first character  of the
  605. * first line being '/*'.  The bi-lingual support allows the  first two char-
  606. * acters to be ':/' as well.
  607. *
  608. * The REXXSYS.SYS device driver will check for the resident version being
  609. * installed, and  if  this  is  a normal REXXPC88 program, an error message
  610. * will be displayed.  However,  if this is a bi-lingual batch file, control
  611. * will be passed on to DOS as normal.
  612. *
  613. * Following is the pseudo code for the device driver operation:
  614.  
  615.  
  616. Appendix D. Installation and Use                                       58
  617. *     if first char = '/' then
  618. *       if resident version installed
  619. *          process as REXXPC88 program
  620. *       else
  621. *          issue error message
  622. *     else
  623. *       if first two chars are ':/' then
  624. *         if resident version installed
  625. *            process as REXXPC88 program
  626. *         else
  627. *            process as DOS batch file
  628. *     else
  629. *       process as DOS batch file
  630. *
  631. *  An example batch file using this feature follows:
  632. *
  633. *   :/*  this is a bi-lingual REXXIBM program
  634. *   echo off
  635. *   goto notinstalled
  636. *              end of REXXIBM normal comment */
  637. *   'echo off'
  638. *   say 'Running as REXXPC88 program'
  639. *   parse source . .  fname
  640. *   say 'We were started from' fname
  641. *   say 'It looks like this'
  642. *   'dir' fname
  643. *   exit
  644. *   /*
  645. *   :notinstalled
  646. *   echo Running as Dos batch file
  647. *   echo We were started from %0
  648. *   echo It looks like this
  649. *   dir %0
  650. *   :*/
  651. *
  652.  
  653. THE DISTRIBUTION DISKETTE
  654.  
  655.  
  656. The REXXPC88 distribution diskette contains these files:
  657.  
  658. 1.  REXXIBMR.EXE ── the resident version
  659. 2.  REXXIBM.EXE ── the standalone version
  660. 3.  REXXSYS.SYS ── the new interface for all DOS versions 2.0 thru 3.2
  661.     batch file processors for resident version.
  662.  
  663.     Note: Use of this device driver requires NO patches to COMMAND.COM.
  664. 4.  REXX88S.BAT ── a sample REXX88 program
  665. 5.  REXX88EX.ASM ── a sample REXX88 extension program
  666.  
  667. If you do not intend to use the resident version, read no further.
  668. REXXIBM.EXE is the only file you need.  (You may wish to execute the
  669. sample program by typing "REXXIBM REXX88S").
  670.  
  671. If you intend to use the resident version, the next section describes how
  672. to install it.
  673.  
  674.  
  675.  
  676. INSTALLING THE RESIDENT VERSION
  677.  
  678.  
  679. To install REXXPC88 on your system follow these instructions carefully:
  680.  
  681. If you have already installed the resident version, to upgrade to this
  682. release, just copy the new REXXIBMR.EXE module to the appropriate direc-
  683. tory, and follow your normal startup procedures.
  684.  
  685. Note: To users who have applied the patches, the new device driver RE-
  686. QUIRES that the patched copy of COMMAND.COM be removed from your system.
  687. Please copy the original from your DOS distribution diskette before con-
  688. tinuing.
  689.  
  690.  
  691.  
  692.  
  693. Appendix D. Installation and Use                                       59
  694. The use of the new device driver REXXSYS.SYS requires no patches to
  695. COMMAND.COM, so the installation is easier and more stable.
  696.  
  697. 1.  Add the following line to the file named "CONFIG.SYS" on your boot-
  698.     diskette (or create the file if it doesn't already exist).
  699.  
  700.         DEVICE=REXXSYS.SYS
  701.  
  702.     Note that you must include a pathname if you have placed REXXSYS.SYS
  703.     in a directory other than the root directory.
  704.  
  705.     Note: Please insure that if you use ANSI.SYS or any ANSI.SYS re-
  706.     placement that the REXXSYS.SYS line is located after the ANSI line in
  707.     the CONFIG.SYS file.  This is to insure that control-break will be
  708.     handled correctly.
  709. 2.  Reboot your machine using the boot-diskette.
  710. 3.  Try executing the file called REXX88S.BAT.  You should see the message
  711.  
  712. *       REXX isn't installed
  713.  
  714.     This indicates that the installation of the device driver was com-
  715.     pleted correctly, but that the main program isn't resident yet.
  716. 4.  Now type
  717.  
  718.         REXXIBMR
  719.  
  720.     to install the main program as a resident extension to DOS.  Execute
  721.     REXX88S.BAT again.  This time you should see:
  722.  
  723.         REXX88 is up and running!
  724.  
  725.     You've successfully installed REXXIBM.  You may wish to place the
  726.     REXXIBMR command into your AUTOEXEC.BAT file so it always makes itself
  727.     resident.
  728.  
  729.  
  730.  
  731. PROBLEMS
  732.  
  733.  
  734. 1.  The use of the new device driver is getting fairly well tested by now,
  735.     but in some environments you may execute a REXXPC88 program when you
  736.     meant to TYPE it via the DOS TYPE command.  If this should occur,
  737.     please append a message to REXX88 FORUM on IBMPC so that it can be
  738.     corrected.
  739.  
  740.  
  741.  
  742.  
  743.  
  744.  
  745.  
  746.  
  747.  
  748.  
  749.  
  750.  
  751.  
  752.  
  753.  
  754.  
  755.  
  756.  
  757.  
  758.  
  759.  
  760.  
  761.  
  762.  
  763.  
  764.  
  765.  
  766.  
  767.  
  768.  
  769.  
  770. Appendix D. Installation and Use                                       60
  771. APPENDIX E. EXTERNAL PROGRAM INTERFACES
  772.  
  773.  
  774.  
  775. This section documents the interfaces by which
  776.  
  777. 1.  A user program may invoke the REXXPC88 interpreter.
  778. 2.  The REXXPC88 inperpreter may invoke user program(s).
  779.  
  780. This section only applies to the "resident" version of REXXPPC88 and is
  781. only for the DOS version.  This section will probably only be of interest
  782. to people with an assembler background and familiarity with DOS internals.
  783.  
  784.  
  785.  
  786. USER PROGRAM INVOCATION OF THE INTERPRETER
  787.  
  788.  
  789. REXXPC88 resides at interrupt 7CH and may be invoked by issuing a software
  790. interrupt to that location.  REXXPC88 operates by interpreting a program
  791. script and returning a string to the caller (usually the DOS command line
  792. handler) whenever an instruction of the form
  793.  
  794.   commandstring argstring1 argstring2...
  795.  
  796. is encountered.
  797.  
  798. From the calling program's prospective, REXXPC88 returns lines of text
  799. as if they were being typed at the keyboard or read from a file.  One line
  800. is returned upon each call to REXXPC88.  Each line of text is terminated
  801. by a carriage return + linefeed + null except the final line, which con-
  802. sists of a eof + null.  Thus the following REXXPC88 program
  803.  
  804.   /* Simple program */
  805.   x = 'three'
  806.   y = 'six'
  807.   'one two' x
  808.   'four five' y
  809.  
  810. would return the following three lines upon successive calls:
  811.  
  812.   one two three 0D 0A 00
  813.   four five six 0D 0A 00
  814.   1A 00
  815.  
  816. The register conventions for invoking REXXPC88 are as follows:
  817.  
  818.  
  819.  
  820. Initialization call
  821.  
  822.  
  823. This call tells REXXPC88 to throw away whatever program he is currently
  824. interpreting (if any) and prepare himself to interpret a new program.
  825.  
  826.  
  827.  
  828. Values taken:
  829.  
  830.  
  831. AX        0000
  832. DS:SI     points to null terminated name of REXXPC88 program to be exe-
  833.           cuted.
  834. EB:BX     points to null terminated argument string to be passed to the
  835.           program.
  836. DX:DI     points  to  an  ENVIRONMENT  control  block  in  the  following
  837.           format:
  838.           DW        offset in segment to signature string
  839.  
  840.                     The segment is that contained in DX and the signature
  841.                     is the UPPER CASE ASCIIZ string "REXX".
  842.  
  843.                     In MASM this string would be defined as db 'REXX',0
  844.           DW        offset in segment to environment name ASCIIZ string
  845.  
  846.  
  847. Appendix E. External Program Interfaces                                61
  848.                     The segment is that contained in DX.
  849.  
  850.                     In MASM this string could be defined as db 'MYENV',0
  851.  
  852.                     Note: The environment name will be truncated if
  853.                     longer  than 32 characters.
  854.           DW        offset in segment to the file extension ASCIIZ string
  855.  
  856.                     This segment is that contained in DX.
  857.  
  858.                     In MASM this string could be defined as db 'CMD',0
  859.  
  860.                     This allows the REXX processor to process files with
  861.                     extensions OTHER than "BAT".
  862.           DW        word value of 0 or non-zero.
  863.  
  864.                     This controls the searching of the path for commands
  865.                     that might be REXX programs. 0 means no search made,
  866.                     non-zero means search first.
  867.           DW        x'AAAA'
  868.  
  869.                     This is a signature that allows REXXPC88 to call your
  870.                     own defined routine when a command expression needs
  871.                     to be processed.
  872.           DD        Segment:offset (standard INTEL format) of environment
  873.                     work buffer, the first double word of the buffer MUST
  874.                     be the entry point address of the environment service
  875.                     routine to be called.  The rest of the buffer may be
  876.                     used in any way you choose and will NOT be examined or
  877.                     modified by REXXPC88.
  878.  
  879.  
  880.  
  881. Environment Service routine parameters and return codes.
  882.  
  883.  
  884. When this entry point is called,  the  following register conditions
  885. exist:
  886.  
  887. No registers need be saved or restored (except SS:SP obviously for the
  888. RET instruction). You will guaranteed that at least 128 words of stack
  889. space are available when the call takes place.
  890.  
  891. Where noted the return code from this service routine is placed in AX
  892. before issuing the RET instruction and is a SIGNED number.
  893.  
  894.  
  895. ES:DI     points to buffer passed on init call (address following x'AAAA'
  896.           signature).
  897.  
  898. AX        Contains the function code described as follows:
  899.  
  900.           0         Command string to execute in DS:DX.  The string is in
  901.                     ASCIIZ   format   with   the   last   three   bytes
  902.                     x'0d',x'oa',x'00' (i.e., that is a carriage return,
  903.                     linefeed and binary zero are appended to the text of
  904.                     the string returned from the normal REXXPC88 ex-
  905.                     pression evaluator.
  906.  
  907.                     On Exit a return code is expected in AX and will be
  908.                     used to set the REXXPC88 special variable RC.
  909.  
  910.                     Return codes should be designed such that the fol-
  911.                     lowing general rules apply:
  912.  
  913.                     AX less than 0 Invalid command string
  914.  
  915.                     AX equal to 0 Command string executed successfully
  916.  
  917.                     AX greater than 0 Command string presents valid com-
  918.                               mand, but it could not be executed for some
  919.                               reason, (i.e., syntax error).
  920.  
  921.  
  922.  
  923.  
  924. Appendix E. External Program Interfaces                                62
  925.           1         REXXPC88 is about to execute a DOS program in the
  926.                     background on behalf of the program running (i.e.
  927.                     ADDRESS DOS expression was issued), and your program
  928.                     should free any memory (via DOS function x'4A') pos-
  929.                     sible.  No notification will be made of background
  930.                     program termination, but is implied if another AX=0
  931.                     call is made or the int 7C interpret call returns.
  932.  
  933.                     On exit no return code is expected or used.
  934.  
  935.           2         REXXPC88 is about to output some data to the console
  936.                     on behalf of the program running.  This is a no-
  937.                     tification only, so that you may be aware that your
  938.                     display screen may become overwritten.  This text
  939.                     display will be made with standard DOS write to han-
  940.                     dle 0 calls and may cause the screen to scroll.
  941.  
  942.                     On Exit a return code is expected in AX and may take
  943.                     one of the three following values:
  944.  
  945.                     -1        Environment routine will process the text
  946.                               of any message to display.  This provides
  947.                               the opportunity for the environment to
  948.                               "window" the text or whatever.
  949.  
  950.                     0         Environment will process screen updates at
  951.                               the end of program execution.  All text
  952.                               outputs should be processed normally by
  953.                               REXXPC88.
  954.  
  955.                     1         The environment wants notification each
  956.                               time a write is about to occur so that any
  957.                               state information may be saved.  Please note
  958.                               that this is a NOTIFICATION call only.
  959.  
  960.                               Note: This is the default method of inter-
  961.                               facing to your program.
  962.  
  963.           3         REXXPC88 is about to output some data to the display
  964.                     console on behalf of the program currently running.
  965.                     You have requested to control the display of any such
  966.                     text by responding AX=-1 to a previous call AX=2.  On
  967.                     entry DS:DX points to the ASCIIZ text of the data
  968.                     about to be output and MAY contain control characters
  969.                     such as carriage return, linefeed and others.  The
  970.                     length of this text is unknown but is terminated at
  971.                     the FIRST byte of binary zero (x'00').
  972.  
  973.                     BX will contain 1 of 2 values and indicates whether
  974.                     the line currently being output is complete.  If BX=1
  975.                     your routine should process a carriage return
  976.                     linefeed equivalent after displaying the text data.
  977.                     Otherwise more data will be sent on another AX=3
  978.                     call.
  979.  
  980.                     On Exit AX is expected to contain one of the following
  981.                     return codes:
  982.  
  983.                     0         display text processed by environment rou-
  984.                               tine.
  985.  
  986.                     -1        Environment routine could not display text,
  987.                               REXXPC88 should process it normally.
  988.  
  989.           4         Console read request.  REXXPC88 is about to read some
  990.                     data from the system console on behalf of the program
  991.                     currently running.  You have requested to control the
  992.                     display  of  any text by responding AX=-1 to a
  993.                     previous call AX=2.  On entry DS:DX points to the
  994.                     output buffer, CX contains the maximum size of the
  995.                     buffer, and BX contains the echo status flag. If BX=1
  996.                     then characters should be echoed as they are read.
  997.                     If BX=0 then no echoing should take place.  On return
  998.                     AX is expected to contain one of the following return
  999.                     codes:
  1000.  
  1001. Appendix E. External Program Interfaces                                63
  1002.                     0 or greater input read is in buffer at DS:DX and is
  1003.                               of this length.
  1004.  
  1005.                               Note:  The carriage return is NOT counted
  1006.                               in this length.  And extended ASCII codes
  1007.                               should have the high order bit turned on
  1008.                               x'80'.
  1009.  
  1010.                     -1        Environment routine could not process read;
  1011.                               REXXPC88 should process it normally.
  1012.  
  1013.  
  1014.  
  1015.  
  1016.  
  1017.  
  1018.  
  1019.  
  1020.  
  1021.  
  1022.  
  1023.  
  1024.  
  1025.  
  1026.  
  1027.  
  1028.  
  1029.  
  1030.  
  1031.  
  1032.  
  1033.  
  1034.  
  1035.  
  1036.  
  1037.  
  1038.  
  1039.  
  1040.  
  1041.  
  1042.  
  1043.  
  1044.  
  1045.  
  1046.  
  1047.  
  1048.  
  1049.  
  1050.  
  1051.  
  1052.  
  1053.  
  1054.  
  1055.  
  1056.  
  1057.  
  1058.  
  1059.  
  1060.  
  1061.  
  1062.  
  1063.  
  1064.  
  1065.  
  1066.  
  1067.  
  1068.  
  1069.  
  1070.  
  1071.  
  1072.  
  1073.  
  1074.  
  1075.  
  1076.  
  1077.  
  1078. Appendix E. External Program Interfaces                                64
  1079. Example Environment control block in MASM
  1080.  
  1081.  
  1082.   signature       db      'REXX',0
  1083.   envname         db      'MYENV',0
  1084.   envextension    db      'CMD',0
  1085.  
  1086.   savebuf         dw      offset myproc   ; entry point offset
  1087.   entryseg        dw      0               ; entry point segment
  1088.                   dw      20 dup(0)       ; set up ADDRESS
  1089.                                           ; save area buffer
  1090.  
  1091.   cb              dw      offset signature
  1092.                   dw      offset envname
  1093.                   dw      offset envextension
  1094.                   dw      1
  1095.                   dw      0AAAAh
  1096.                   dw      offset savebuf
  1097.   savebufbs       dw      0               ; used for segment address
  1098.                   .
  1099.                   .
  1100.                   .
  1101.                   mov     dx,ds
  1102.                   mov     savebufbs,dx
  1103.                   mov     ax,cs
  1104.                   mov     entryseg,ax
  1105.                   mov     di,offset cb
  1106.                   .
  1107.                   .
  1108.                   .
  1109.                   mov     ax,0
  1110.                   int     7ch
  1111.                   .
  1112.                   .
  1113.  
  1114.  
  1115.  
  1116.  
  1117.  
  1118.  
  1119.  
  1120.  
  1121.  
  1122.  
  1123.  
  1124.  
  1125.  
  1126.  
  1127.  
  1128.  
  1129.  
  1130.  
  1131.  
  1132.  
  1133.  
  1134.  
  1135.  
  1136.  
  1137.  
  1138.  
  1139.  
  1140.  
  1141.  
  1142.  
  1143.  
  1144.  
  1145.  
  1146.  
  1147.  
  1148.  
  1149.  
  1150.  
  1151.  
  1152.  
  1153.  
  1154.  
  1155. Appendix E. External Program Interfaces                                65
  1156. Example user environment routine shell.
  1157.  
  1158.   myproc          proc    far
  1159.                   cmp     ax,0            ; command execution ?
  1160.                   jne     try_freemem     ; see if free mem request
  1161.                   .
  1162.                   process command in DS:DX
  1163.                   .
  1164.                   mov     ax,rc
  1165.                   jmp     env_done
  1166.   try_freemem:
  1167.                   cmp     ax,1            ; free memory request?
  1168.                   jne     try_notify      ; no, try notify
  1169.                   .
  1170.                   free memory if possible
  1171.                   jmp     env_done        ; note no return code in ax
  1172.   try_notify:     cmp     ax,2            ; notify of text?
  1173.                   jne     try_text        ; no, see if text
  1174.                                           ; message request
  1175.                   .
  1176.                   process notify
  1177.                   .
  1178.                   mov     ax,notify_rc    ; set return code
  1179.                   jmp     env_done
  1180.   try_text:       cmp     ax,3
  1181.                   jne     try_read
  1182.                   .
  1183.                   process text message in DS:DX
  1184.                   BX contains end of line status
  1185.                   .
  1186.                   mov     ax,write_rc     ; set return code
  1187.                   jmp     env_done
  1188.   try_read:       cmp     ax,4
  1189. *                   jne   bad_operation
  1190.                   .
  1191.                   process read request into DS:DX
  1192.                   BX contains echo status
  1193.                   CX contains max read count
  1194.                   .
  1195.                   mov     ax,read_rc      ; set return code
  1196. *                 jmp     env_done
  1197. * bad_operation:
  1198. *                 mov     ax,-1
  1199.   env_done:
  1200.                   ret
  1201.   myproc          endp
  1202.  
  1203. Note: The default environment name and extension are 'DOS' and 'BAT' re-
  1204. spectively.  The default name is selected if the signature pointed to by
  1205. the first word at DX:DI is NOT 'REXX'.
  1206.  
  1207. The  name  of  the current environment can be found using the ADDRESS
  1208. built-in function.
  1209.  
  1210.  
  1211.  
  1212. Values returned:
  1213.  
  1214.  
  1215. Nothing is returned.  The only way to tell if the program exists and can
  1216. be executed is by examining a value returned by the program in the next
  1217. call described below.  If the program returns an end of program indication
  1218. and a string was expected instead, it means that the program was not found
  1219. or could not be executed for some reason.
  1220.  
  1221.  
  1222.  
  1223. Register use:
  1224.  
  1225.  
  1226. All registers except SS and SP are destroyed.  The caller must save any
  1227. other registers of interest.
  1228.  
  1229.  
  1230.  
  1231.  
  1232. Appendix E. External Program Interfaces                                66
  1233. Interpretation call
  1234.  
  1235.  
  1236. This call tells REXXPC88 to interpret the REXXPC88 program until a value
  1237. is produced.
  1238.  
  1239.  
  1240.  
  1241. Values taken:
  1242.  
  1243.  
  1244. AX        0001
  1245.  
  1246.  
  1247.  
  1248. Values returned:
  1249.  
  1250.  
  1251. DS:DX     points to a result string, terminated by a CR + LF + NULL.  The
  1252.           final result string (which marks the end of the program) con-
  1253.           sists of nothing but EOF + NULL.  REXXPC88 will continue to re-
  1254.           turn this "end of program" string until re-initialized via an
  1255.           AX=0000 call as described above.
  1256.  
  1257.  
  1258.  
  1259. Register use:
  1260.  
  1261.  
  1262. All registers except SS and SP are destroyed.  The caller must save any
  1263. other registers of interest.
  1264.  
  1265.  
  1266.  
  1267. Termination call
  1268.  
  1269.  
  1270. This call allows  resident  REXXPC88 extensions to terminate execution of
  1271. a REXXPC88 program, typically after detecting an error.
  1272.  
  1273.  
  1274.  
  1275. Values taken:
  1276.  
  1277.  
  1278. AX        0002
  1279. DS:SII    points to null terminated string to be displayed as an error
  1280.           message before terminating the REXXPC88 program.
  1281.  
  1282.  
  1283.  
  1284. Values returned:
  1285.  
  1286.  
  1287.           never returns to caller.  Terminates the REXXPC88 program and
  1288.           returns control to DOS.
  1289.  
  1290.  
  1291.  
  1292. Load call
  1293.  
  1294.  
  1295. This call tells REXXPC88 to look up a program variable and return its
  1296. current value (if any).
  1297.  
  1298.  
  1299.  
  1300. Values taken:
  1301.  
  1302.  
  1303. AX        0003
  1304. DS:SI     points to null terminated name of REXXPC88 program variable.
  1305.  
  1306.  
  1307.  
  1308.  
  1309. Appendix E. External Program Interfaces                                67
  1310. Values returned:
  1311.  
  1312.  
  1313. DS:DX     points to the null terminated string value of the program vari-
  1314.           able.  DX is zero if the program variable is currently unde-
  1315.           fined.  This string is in REXXPC88's data area and must be
  1316.           treated read-only.
  1317.  
  1318.  
  1319.  
  1320. Register use:
  1321.  
  1322.  
  1323. All registers except SS and SP are destroyed.  The caller must save any
  1324. other registers of interest.
  1325.  
  1326.  
  1327.  
  1328. Store call
  1329.  
  1330.  
  1331. This call tells REXXPC88 to store a null terminated string as the value
  1332. of a program variable.
  1333.  
  1334.  
  1335.  
  1336. Values taken:
  1337.  
  1338.  
  1339. AX        0004
  1340. DS:SI     points to null terminated name of REXXPC88 program variable.
  1341. ES:BX     points to null terminated string to be assigned to the variable.
  1342.  
  1343.  
  1344.  
  1345. Values returned:
  1346.  
  1347.  
  1348. Nothing is returned. The string is copied into REXXPC88's data dictionary.
  1349. If there is insufficient storage to store the string, REXXPC88 terminates
  1350. execution of the program with an error message and returns to DOS.
  1351.  
  1352.  
  1353.  
  1354. Register use:
  1355.  
  1356.  
  1357. All registers except SS and SP are destroyed.  The caller must save any
  1358. other registers of interest.
  1359.  
  1360.  
  1361.  
  1362. REXXPC88 INVOCATION OF USER WRITTEN EXTENSIONS
  1363.  
  1364.  
  1365. REXXPC88 resolves procedure and function references according to the
  1366. following list:
  1367.  
  1368. 1.  If a routine having the specified name exists as a label in th cur-
  1369.     rent REXXPC88 program then control is passed to that label.
  1370. 2.  If a built-in REXXPC88 routine having the specified name exists, then
  1371.     control is passed to that built-in routine.
  1372. 3.  An interrupt 7CH is issued (AX = 0005), passing the name of the rou-
  1373.     tine sought and the arguments to that routine.  User code at that
  1374.     interrupt location may choose to "answer" the interrupt with a result
  1375.     string, in which case that string is returned as the value of the
  1376.     function.
  1377. 4.  Finally, REXXPC88 looks for a REXXPC88 program on disk by checking
  1378.     each directory named in the current PATH environment string. If found,
  1379.     that routine is loaded and given control.  When it terminates, the
  1380.     string value it produced via a return or exit instruction is returned
  1381.     as the value of the function.
  1382. 5.  If none of the above yield a value, REXXPC88 issues an "undefined
  1383.     routine" error and terminates the program.
  1384.  
  1385.  
  1386. Appendix E. External Program Interfaces                                68
  1387. The convention I've adopted for adding extensions to REXXPC88 is to allow
  1388. users to "chain" their code onto interrupt 7CH and issue a "terminate but
  1389. remain resident" DOS call.  The instructions initially placed by REXXPC88
  1390. at that location to answer a "call extension" request do nothing but re-
  1391. turn a NIL pointer, indicating that no extensions have answered the in-
  1392. terrupt.
  1393.  
  1394. ∙   User code is expected to watch for a "call extension" request (AX =
  1395.     0005) and to answer the interrupt by returning a string pointer to a
  1396.     result value.
  1397.  
  1398. ∙   If AX <> 0005 then control must be passed to the next routine in the
  1399.     interrupt chain, preserving all registers.
  1400.  
  1401. ∙   If AX == 0005 and the user's code chooses not to answer the interrupt
  1402.     because the function named in the parameter block is unrecognized then
  1403.     control must be passed to the next routine in the chain, but only the
  1404.     values of AX, SS, and BP need be preserved.
  1405.  
  1406.  
  1407.  
  1408. Values passed in:
  1409.  
  1410.  
  1411. AX        0005
  1412. SS:BP     points to a C stackframe containing a two-byte pointer to the
  1413.           null terminated function name, a  two-byte  integer specifying
  1414.           the number of arguments, and  a  two-byte pointer to an array
  1415.           of pointers (each two bytes)  to the arguments (each argument
  1416.           is a null terminated string).
  1417.  
  1418.  
  1419.  
  1420. Values passed out:
  1421.  
  1422.  
  1423. DS:SI     must point to a null terminated result string.  A pointer of
  1424.           NIL (DS == 0, SI == 0) is reserved by REXXPC88 and indicates
  1425.           that "no REXXPC88 extensions answered the function".
  1426.  
  1427.  
  1428.  
  1429. Register use:
  1430.  
  1431.  
  1432. All registers except SS, SP, and BP are available for use.
  1433.  
  1434.  
  1435.  
  1436. Stack use:
  1437.  
  1438.  
  1439. Since the amount of REXXPC88 stack space remaining for growth can't be
  1440. ascertained by the user extension program,  the user may wish to switch
  1441. to a local stack if he requires more than about 128 bytes of stack growth.
  1442.  
  1443. A sample REXXPC88 extension program is available on the IBMPC conferencing
  1444. disk in a file named "REXX88EX ASMBIN".
  1445.  
  1446.  
  1447.  
  1448. Queue call
  1449.  
  1450.  
  1451. This call tells REXXPC88 to place data on the data or external interrupt
  1452. queue either FIFO or LIFO.
  1453.  
  1454.  
  1455.  
  1456. Values taken:
  1457.  
  1458.  
  1459. AX        0006
  1460. BH        00 Internal data queue accessible via PULL and PARSE PULL
  1461.  
  1462.  
  1463. Appendix E. External Program Interfaces                                69
  1464. BH        01 External interrupt queue accessible via LINEIN(EXQUE)
  1465. BL        00 Queue data FIFO on selected queue
  1466. BL        01 Queue data LIFO on selected queue
  1467. DS:SI     points to null terminated string to be queued.
  1468.  
  1469.           For the Internal data queue a string may not exceed 127 char-
  1470.           acters.
  1471.  
  1472.           For the External interrupt queue a string may not exceed
  1473.           available storage.
  1474.  
  1475.  
  1476.  
  1477. Values returned:
  1478.  
  1479.  
  1480. AX
  1481.  
  1482. 0         Message queued successfully.
  1483. 1         No REXXPC88 program running at current time. Message not queued.
  1484. 2         Not enough storage available for message.  Message not queued.
  1485. 3         Either BH (queue number) or BL (FIFO/LIFO flag) out of range.
  1486.           Message not queued.
  1487.  
  1488.  
  1489.  
  1490. Register use:
  1491.  
  1492.  
  1493. All registers except SS and SP are destroyed.  The caller must save any
  1494. other registers of interest. AX contains return code from service request.
  1495.  
  1496.  
  1497.  
  1498. Loaded call
  1499.  
  1500.  
  1501. This call provides a way for a REXXPC88 extension to find out if a copy
  1502. is already loaded, and to exchange information with a resident version.
  1503.  
  1504.  
  1505.  
  1506. Values taken:
  1507.  
  1508.  
  1509. AX        0007
  1510. SS:BP     points to a C stack frame containing  a  two-byte pointer to
  1511.           the null terminated name of the REXXPC88 extension.
  1512.  
  1513.  
  1514.  
  1515. Values returned:
  1516.  
  1517.  
  1518. If the extension is already loaded, then DS:SI points to an ASCIIZ string
  1519. '1', and other registers are used as desired by the extension to commu-
  1520. nicate with its non-resident copy.  (Generally, this involves pointing
  1521. ES:BX to the resident portion's entry point).  If the extension is not
  1522. yet resident, then DS:SI points to an ASCIIZ '0'.
  1523.  
  1524.  
  1525.  
  1526. Register use:
  1527.  
  1528.  
  1529. All registers except SS, SP and BP are available for use.
  1530.  
  1531.  
  1532.  
  1533.  
  1534.  
  1535.  
  1536.  
  1537.  
  1538.  
  1539.  
  1540. Appendix E. External Program Interfaces                                70
  1541. Reserved call
  1542.  
  1543.  
  1544. This call is reserved for communication between REXXSYS.SYS and REXXIBMR.
  1545.  
  1546.  
  1547.  
  1548. Values taken:
  1549.  
  1550.  
  1551. AX        0008
  1552.  
  1553.  
  1554.  
  1555. Values given:
  1556.  
  1557.  
  1558. NONE
  1559.  
  1560.  
  1561.  
  1562. Installed call
  1563.  
  1564.  
  1565. This call provides external applications a way to determine if REXXIBMR
  1566. is installed.
  1567.  
  1568.  
  1569.  
  1570. Values taken:
  1571.  
  1572.  
  1573. AX        0009
  1574.  
  1575.  
  1576.  
  1577. Values returned:
  1578.  
  1579.  
  1580. AX=FFFF   REXXIBMR is not installed
  1581. AX=AAAA   REXXIBMR is installed
  1582.  
  1583. Note: It is assumed that your application will inspect the value of the
  1584. 7C interrupt vector prior to issuing this interrupt.  If the vector is
  1585. 0000:0000 then REXXIBMR is not installed and this function will cause the
  1586. system to crash.
  1587.  
  1588.  
  1589.  
  1590. * Uninstall resident version
  1591. *
  1592. *
  1593. * This call is used to uninstall a resident version
  1594. *
  1595. *
  1596. *
  1597. * Values taken:
  1598. *
  1599. *
  1600. * AX        000A
  1601. * BX        AAAA
  1602. *
  1603. *
  1604. *
  1605. * Values returned:
  1606. *
  1607. *
  1608. * AX = 0    Resident version uninstalled
  1609. * AX = 1    Resident version cannot uninstall,  as  one interrupt vector has
  1610. *           been modified by some other program in a non-conforming manner.
  1611. * AX = FFFF The  installed  resident  version does NOT support the uninstall
  1612. *           request code (i.e., it is pre 0.55 level).
  1613.  
  1614.  
  1615.  
  1616.  
  1617. Appendix E. External Program Interfaces                                71
  1618. APPENDIX F. REXXPC88 VS. REXX370
  1619.  
  1620.  
  1621.  
  1622. Every attempt has been made to maintain consistency between REXXPC88 and
  1623. its big brother REXX370, within the contexts of a small machine environ-
  1624. ment.
  1625.  
  1626. * The FIND function is called WORDPOS as the REXX 3.5 spec defines.  Please
  1627. * see the WORDPOS definition in the built-in function section of this docu-
  1628. * ment.
  1629. *
  1630. * Note:  Please note that the parameter order for WORDPOD is different than
  1631. * that of the REXX370 FIND function.
  1632. *
  1633. * A "difference"  has  been  discovered in the processing of quoted literal
  1634. * strings.  The REXX 3.5 spec says that quoted literal strings MUST be con-
  1635. * tained completely on the same line, and if not,  is  treated as an error.
  1636. * Apparently REXX370 adds the missing quote instead of reporting the error.
  1637.  
  1638. REXXPC88 is now at almost full language spec and should provide for easy
  1639. transfer of programs between PC/DOS and VM.  Very minor differences still
  1640. exist, but are mainly in the error recovery functions (i.e., SIGNAL ON
  1641. SYNTAX, etc.).
  1642.  
  1643. Some built-in functions remain to be done.  These are the ones that could
  1644. conflict with the current C language implementation (i.e., BITXOR,
  1645. CHARIN, etc.).
  1646.  
  1647. Also those whose performance impacts are not yet evaluated (i.e., LINEIN,
  1648. SOURCELINE, etc.).
  1649.  
  1650. This implementation is in the process of being upgraded to full REXX370
  1651. 3.5 level.  If you see something not mentioned below, please bring it to
  1652. my attention.
  1653.  
  1654.  
  1655.  
  1656. Missing Features
  1657.  
  1658.  
  1659. 1.  Some built-in functions that might result in a byte of binary zero
  1660.     being returned in a string.  As the current versions of REXXPC88 are
  1661.     written in C, the default string terminator is a byte of binary zero.
  1662.  
  1663.  
  1664.  
  1665. Added Features
  1666.  
  1667.  
  1668. 1.  Primitive file management functions (directory(), size(), seek(),
  1669.     read(), and write()) and console I/O functions (ask()) are included
  1670.     as part of the REXXPC88, although they are not part of the language
  1671.     itself.
  1672.  
  1673.  
  1674.  
  1675.  
  1676.  
  1677.  
  1678.  
  1679.  
  1680.  
  1681.  
  1682.  
  1683.  
  1684.  
  1685.  
  1686.  
  1687.  
  1688.  
  1689.  
  1690.  
  1691.  
  1692.  
  1693.  
  1694. Appendix F. REXXPC88 vs. REXX370                                      72
  1695. APPENDIX G. BUGS AND LIMITATIONS
  1696.  
  1697.  
  1698.  
  1699. REXXPC88 is still under development.  This section discusses known bugs
  1700. or limitations.  Please report any others you find to me.
  1701.  
  1702. 1.  The operation of the parse instruction should NOT differ  from that
  1703.     of the REXX370 version.   If you discover a difference, please tell
  1704.     me about it.
  1705. 2.  The read() function is limited to a line size of 256 bytes or the
  1706.     setting of the number on the command line preceding the 'r' parm.
  1707.     ((512r sets the read size to 512 characters.
  1708.  
  1709.     Note:  There is a difference between the resident and non-resident
  1710.     versions concerning the read size parameter.  For the non-resident
  1711.     version unless otherwise specified the read size will default to 256.
  1712.     For the resident version the default read size will be reset by this
  1713.     parameter and will be used unless specifically reset. The minimum size
  1714.     is 132.
  1715. 3.  The 'maximum number of open files' specified on the REXXPC88 command
  1716.     line must be less than the number of files specified in your
  1717.     'config.sys' file since DOS needs file descriptors to perform program
  1718.     execution and command line redirection.
  1719. 4.  Nesting of procedure and function calls is limited to a depth of 70.
  1720. 5.  Argument lists are limited tto 10 arguments.
  1721. 6.  When running under PC-DOS, pressing the BREAK key (either Control-
  1722.     Break or Control-C)  will cause the batch file to be terminated at
  1723.     the next clause boundary.  This condition can be trapped by use of the
  1724.     SIGNAL ON HALT instruction.  If SIGNAL ON HALT is not used, a message
  1725.     will be issued, and the batch file terminated.
  1726.  
  1727.     The DOS "Terminate Batch File Y/N" prompt will NOT appear.
  1728.  
  1729.     If Control-C is pressed, at the next DOS function causing the break
  1730.     to be recognized, a Control-C character will be printed prior to the
  1731.     batch file recognition of the key press.  This is a DOS issue.  This
  1732.     condition does NOT occur with Control-Break.
  1733.  
  1734.     This break-trapping now should allow one to safely terminate a
  1735.     REXXPC88 program without rebooting.  If you should discover a problem,
  1736.     please let me know.
  1737. 7.  Command line redirection does not work with the resident version of
  1738.     REXXPC88.  Thus it is impossible to direct the output of a REXXPC88
  1739.     program executed by the resident version to the printer, for example.
  1740.     (Use of redirection operators within the REXXPC88 program works fine
  1741.     though).
  1742.  
  1743.     This behavior seems to be due to the way DOS handles command line
  1744.     redirection, since the standalone version of REXXPC88 does not have
  1745.     this problem.
  1746. 8.  DOS's treatment of 'environment' space leaves much to be desired and
  1747.     causes the following difficulties when using the SET and PATH com-
  1748.     mands:
  1749.     a.  The resident version of REXXPC88 now points to and uses the master
  1750.         copy of the environment owned by COMMAND.COM.  You will notice
  1751.         that some programs that try to identify resident extensions by
  1752.         their environment (like SWAP), will not be able to identify res-
  1753.         ident REXXPC88.
  1754.     b.  Notice that any changes in the environment (i.e. CD or PATH) made
  1755.         during execution of standalone REXXPC88 programs do not persist.
  1756.         REXXPC88 invokes a temporary copy of the command executor to
  1757.         perform DOS commands, when the command is finished the temporary
  1758.         executor and its modified environment are thrown away.
  1759. 9.  Execution of a DOS batch file from within a REXXPC88 program is NOT
  1760.     supported, as DOS only allows ONE batch file to be executing at any
  1761.     one time.  This would cause termination of the current REXXPC88 pro-
  1762.     gram.
  1763.  
  1764.     PC/DOS 3.3 supports nested DOS batch files thru the CALL instruction.
  1765.     REXXPC88 does NOT support this feature.
  1766.  
  1767.  
  1768.  
  1769.  
  1770.  
  1771. Appendix G. Bugs and Limitations                                       73
  1772. APPENDIX H. SAMPLE PROGRAM
  1773.  
  1774.  
  1775.  
  1776. /* DISKINFO.BAT
  1777. * This is a demonstration program which counts
  1778. * the number of files in a specified directory
  1779. * and adds up their sizes.  It uses the DOS
  1780. * 'dir' command to create a list of the files
  1781. * and then scans the list to extract the
  1782. * required information.
  1783. *
  1784. * Some examples of how you might invoke it to:
  1785. *  summarize root directory
  1786. *                         DISKINFO A:
  1787. *  summarize directory 'foo'
  1788. *                         DISKINFO A:\FOO
  1789. *  summarize 'asm' files in 'foo'
  1790. *                         DISKINFO A:\FOO\*.ASM
  1791. *
  1792. * Sample directory listing to aid
  1793. * you in understanding this program:
  1794. *                1         2         3
  1795. *       123456789012345678901234567890123456789
  1796. *       ---------------------------------------
  1797. *     1
  1798. *     2  Volume in drive D has no label
  1799. *     3  Directory of  D:\execs
  1800. *     4
  1801. *     5 .            <DIR>      2-15-84   4:30p
  1802. *     6 ..           <DIR>      2-15-84   4:30p
  1803. *     7 DISKINFO BAT     1674   2-21-84   2:03p
  1804. *     8         3 File(s)   1638400 bytes free
  1805. *       ---------------------------------------
  1806. *
  1807.  
  1808. * Acknowledgment to Ray Holland
  1809. * for the ideas used herein.
  1810. */
  1811. /*trace ?r*/
  1812. 'echo off'                      /* suppress DOS screen output */
  1813. 'cls'                           /* clear the screen */
  1814. arg dirname .
  1815. if dirname== '?' then
  1816.   do                            /* give user help if he needs it */
  1817.     say 'Summarize disk usage for specified files of a directory'
  1818.     say
  1819.     say 'Format:   DISKINFO A:          (summarize root)'
  1820.     say '          DISKINFO A:\FOO      (summarize foo directory)'
  1821.     say
  1822.     exit
  1823.   end
  1824.  
  1825. files = 0;                      /* number of files counted       */
  1826. dirs = 0;                       /* number of directories counted */
  1827. spaceused = 0;                  /* space occupied by the files   */
  1828. minsize=''
  1829. maxsize=''
  1830. swchar=''
  1831.  
  1832. curdir=directory()          /* get current drive and directory */
  1833.  
  1834. if dirname=='' then dirname=curdir /* if no name spec use dir */
  1835.  
  1836. if substr(dirname,2,1)¬=':'     /* if no drive spec use default */
  1837.       then dirname=left(curdir,2)  dirname
  1838.  
  1839.  
  1840.  
  1841.  
  1842.  
  1843.  
  1844.  
  1845.  
  1846.  
  1847.  
  1848.   Appendix H. Sample Program                                         74
  1849. curdrive=left(curdir,2)         /* get default drive letter */
  1850.  
  1851. dirdrive=left(dirname,2)        /* get requested drive letter */
  1852.  
  1853. if curdrive¬=dirdrive then do   /* if not the same */
  1854.   dirdrive                      /* switch drives */
  1855.   othdir=directory()        /* get that drives current directory */
  1856. end
  1857.                             /* did requested dir end in backslash */
  1858. if right(dirname,1)¬='\' then swchar='\'   /* no  */
  1859.                          else swchar=''    /* yes */
  1860.  
  1861.                             /* was request for directory contents */
  1862. if dirname==directory(dirname) /* change to directory (if same ok */
  1863.     then swchar=swchar  '*.*'  /* then was directory set filespec */
  1864. else swchar=''                 /* was for full filespec list */
  1865.  
  1866. /* Get the directory information */
  1867. listfile(dirname  swchar,63,fifo) /* list file info to queue */
  1868.  
  1869.  
  1870. say '        DISKINFO'
  1871. /* Scan the directory listing */
  1872. do queued()                     /* for number of files found */
  1873.    parse pull filename filesize fileattr filedate filetime dir
  1874.   select
  1875.    when dir == '<DIR>' then do          /* count directory */
  1876.      if filename¬=='.'& filename¬=='..' then
  1877.        dirs = dirs + 1
  1878.      end
  1879.  
  1880.    when dir == '<VOL>' then nop         /* skip vol entry */
  1881.    otherwise files=files+1              /* was a file count it */
  1882.              spaceused = spaceused + filesize /* and its space */
  1883.              if minsize='' then minsize=filesize
  1884.                            else minsize=min(minsize,filesize)
  1885.              if maxsize='' then maxsize=filesize
  1886.                            else maxsize=max(maxsize,filesize)
  1887.    end
  1888. end
  1889.  
  1890. /* Print a summary */
  1891. say
  1892. say '"'dirname'" contains' files 'files and' dirs 'directories.'
  1893. say
  1894. say 'Storage used = ' spaceused ' bytes ('(spaceused % 1024)'k)'
  1895. say
  1896. if minsize='' then minsize=0
  1897. if maxsize='' then maxsize=0
  1898. say 'Average file size is' spaceused % files 'bytes'
  1899. say 'Minimum file size is 'minsize 'bytes'
  1900. say 'Maximum file size is 'maxsize 'bytes'
  1901. end
  1902. say
  1903. if dirdrive¬=curdrive then do
  1904.     call directory othdir
  1905.     end
  1906. call directory curdir
  1907. exit
  1908.  
  1909.  
  1910.  
  1911.  
  1912.  
  1913.  
  1914.  
  1915.  
  1916.  
  1917.  
  1918.  
  1919.  
  1920.  
  1921.  
  1922.  
  1923.  
  1924.  
  1925. Appendix H. Sample Program                                           75
  1926.  APPENDIX I. SYNTAX DIAGRAMS
  1927.  
  1928.  
  1929.  
  1930. program ::=              instructionlist
  1931.  
  1932. instructionlist ::=      instruction
  1933.                          instructionlist
  1934.  
  1935. instruction ::=          label-instruction
  1936.                          assignment-instruction
  1937.                          keyword-instruction
  1938.                          command-instruction
  1939.  
  1940. label-instruction ::=    name : ;
  1941.  
  1942. assignment-instruction ::= name = expression ;
  1943.  
  1944. keyword-instruction ::=
  1945.  
  1946. DO ; instructionlist END ;
  1947. DO expression ; instructionlist END ;
  1948. DO FOREVER ; instructionlist END ;
  1949. DO name = expression [TO expression
  1950.           [BY expression]] ;
  1951.    instructionlist END ;
  1952. LEAVE ;
  1953. CALL name expressionlist ;
  1954. RETURN ;
  1955. RETURN expression ;
  1956. EXIT ;
  1957. EXIT expression ;
  1958. IF expression [;] THEN [;] instruction
  1959. IF expression [;] THEN [;] instruction
  1960.                   ELSE [;] instruction
  1961. PARSE  upper SOURCE template;
  1962. PARSE  upper VERSION template ;
  1963. PARSE  upper VALUE  expression WITH template ;
  1964. PARSE  upper VAR  varname template ;
  1965. PARSE  upper PULL template ;
  1966. PARSE  upper ARG template ;
  1967. PARSE  upper LINEIN template ;
  1968. PULL   expression
  1969. PUSH   expression
  1970. QUEUE  expression
  1971. NUMERIC DIGITS expression
  1972. NUMERIC FUZZ expression
  1973. NUMERIC FORM SCIENTIFIC
  1974. NUMERIC FORM ENGINEERING
  1975. OPTIONS expression
  1976. SAY expression ;
  1977. TRACE expression ;
  1978. PROCEDURE ;
  1979. PROCEDURE EXPOSE namelist ;
  1980. DROP namelist ;
  1981.  
  1982. command-instruction ::=  expression ;
  1983.  
  1984.  
  1985.  
  1986.  
  1987.  
  1988.  
  1989.  
  1990.  
  1991.  
  1992.  
  1993.  
  1994.  
  1995.  
  1996.  
  1997.  
  1998.  
  1999.  
  2000.  
  2001.  
  2002.   Appendix I. Syntax Diagrams                                        76
  2003. expressionlist ::=    expression
  2004.                       expression , expressionlist
  2005.  
  2006. expression ::=        term operator expression
  2007.                       empty-expression
  2008.  
  2009. term ::=              ( expression )
  2010.                       constant
  2011.                       name
  2012.                       name( expressionlist )
  2013.  
  2014. constant ::=          ' characterlist '
  2015.                       ' hexdigitlist 'x
  2016.                       decimaldigitlist
  2017.  
  2018. operator ::=          abuttal
  2019.                       whitespace
  2020.                       ==
  2021.                       /==
  2022.                       =
  2023.                       <>
  2024.                       <
  2025.                       <=
  2026.                       >
  2027.                       >=
  2028.                       │
  2029.                       &
  2030.                       +
  2031.                       -
  2032.                       *
  2033.                       %
  2034.                       //
  2035.                       /
  2036.                       **
  2037.                       ││
  2038.                       \
  2039.  
  2040. namelist ::=       name
  2041.                    name namelist
  2042.  
  2043. name ::=           simple-name
  2044.                    compound-name
  2045.                    stem
  2046.  
  2047. compound-name ::=  stem subscripts
  2048.  
  2049. stem ::=           simple name .
  2050.  
  2051. subscripts ::=     [ simple-name ]
  2052.                    . [ subscript ]
  2053.  
  2054. simple-name ::=    letter [ letter
  2055.                           │ digit ]...
  2056.  
  2057. characterlist ::=  [ any-character ]...
  2058.  
  2059. hexdigitlist ::=   [0..9 │ a..f │ A..F]...
  2060.  
  2061. decimaldigitlist ::=  [ 0..9 ]...
  2062.  
  2063. letter ::=         a..z │ A..Z
  2064.  
  2065. digit ::=          0..9
  2066.  
  2067.  
  2068.  
  2069.  
  2070.  
  2071.  
  2072.  
  2073.  
  2074.  
  2075.  
  2076.  
  2077.  
  2078.  
  2079.   Appendix I. Syntax Diagrams                                        77
  2080. APPENDIX J. KEYWORDS
  2081.  
  2082.  
  2083.  
  2084. Keywords are no longer reserved except where noted with certain clauses
  2085. and may be used as variable names:
  2086.  
  2087. 1.   do
  2088. 2.   forever
  2089. 3.   leave
  2090. 4.   end
  2091. 5.   call
  2092. 6.   return
  2093. 7.   procedure
  2094. 8.   if
  2095. 9.   then
  2096. 10.  else
  2097. 11.  parse
  2098. 12.  source
  2099. 13.  version
  2100. 14.  value
  2101. 15.  with
  2102. 16.  say
  2103. 17.  trace
  2104. 18.  exit
  2105. 19.  expose
  2106. 20.  drop
  2107. 21.  to
  2108. 22.  by
  2109. 23.  pull
  2110. 24.  push
  2111. 25.  queue
  2112. 26.  var
  2113. 27.  arg
  2114. 28.  numeric
  2115. 29.  digits
  2116. 30.  fuzz
  2117. 31.  form
  2118. 32.  options
  2119.  
  2120.  
  2121.  
  2122.  
  2123.  
  2124.  
  2125.  
  2126.  
  2127.  
  2128.  
  2129.  
  2130.  
  2131.  
  2132.  
  2133.  
  2134.  
  2135.  
  2136.  
  2137.  
  2138.  
  2139.  
  2140.  
  2141.  
  2142.  
  2143.  
  2144.  
  2145.  
  2146.  
  2147.  
  2148.  
  2149.  
  2150.  
  2151.  
  2152.  
  2153.  
  2154.  
  2155.  
  2156. Appendix J. Keywords                                                   78
  2157. APPENDIX K. ERROR MESSAGES
  2158.  
  2159.  
  2160.  
  2161. Here is a list of error messages that you may encounter.  The '%c', "%c',
  2162. and '%s' are replaced by an appropriate number, character, or string,
  2163. respectively.  The messages should be self explanatory, except for the
  2164. "Internal error" message.  The latter indicates that the interpreter found
  2165. itself in an inconsistent state.  I'd like to hear from you if this ever
  2166. happens.
  2167.  
  2168.   DET800 Program '%s' is unreadable",
  2169.   DET801 Input line can't exceed %s characters",
  2170.   DET802 Invalid hex value",
  2171.   DET803 User Cancelled",
  2172.   DET804 Unmatched quote",
  2173.   DET805 Command shell %s not found",
  2174.   DET806 ------------unused----------------
  2175.   DET807 Input line too complicated; please simplify",
  2176.   DET808 Unclosed comment starting in line %s, ending",
  2177.   DET809 %s() didn't return a value",
  2178.   DET810 DO n=x TO y BY z; z must evaluate to a number",
  2179.   DET811 DO n=x TO y BY z for w; w must evaluate to a whole number";
  2180.   DET812 Too many nested calls",
  2181.   DET813 ------------unused----------------
  2182.   DET814 Comma expected in argument list",
  2183.   DET815 DO n=x TO y BY z; x must evaluate to a number",
  2184.   DET816 Unexpected keyword (%s)",
  2185.   DET817 Invalid syntax for PARSE instruction",
  2186.   DET818 Invalid expression",
  2187.   DET819 Invalid PARSE template",
  2188.   DET820 DO n; n must evaluate to a whole number",
  2189.   DET821 Logical value not 0 or 1",
  2190.   DET822 Do n=x To y BY z; n must evaluate to a whole number",
  2191.   DET823 Missing THEN after %s",
  2192.   DET824 No active loop",
  2193.   DET825 Not enough storage %s",
  2194.   DET826 Program '%s' not found",
  2195.   DET827 Non-numeric value (%s) found during expression evaluation",
  2196.   DET828 ------------unused----------------
  2197.   DET829 Procedure name expected",
  2198.  
  2199.   DET830 Can't write output file '%s'",
  2200.   DET831 Unmatched parenthesis in argument list",
  2201.   DET832 Semicolon expected following %s",
  2202.   DET833 DO n=x TO y BY z; y must evaluate to a number",
  2203.   DET834 Term expected after operator (%s)",
  2204.   DET835 Can't use more than %s arguments",
  2205.   DET836 Can't use more than %s files",
  2206.   DET837 ------------unused----------------
  2207.   DET838 Undefined routine (%s)",
  2208.   DET839 Incomplete DO or IF block",
  2209.   DET840 ------------unused----------------
  2210.   DET841 Variable name expected",
  2211.   DET842 Invalid argument or wrong number of arguments",
  2212.   DET843 Internal error in '%s'",
  2213.   DET844 Invalid trace flag (%s)",
  2214.   DET845 '%s' expected instead of '%s'",
  2215.   DET846 Division by zero",
  2216.   DET847 Control variable name for \"%s %s\" not found",
  2217.   DET848 Labelname expected",
  2218.   DET849 Labelname could not be found",
  2219.   DET850 WHEN or OTHERWISE expected",
  2220.   DET851 OTHERWISE expected",
  2221.   DET852 Numeric Overflow/Underflow during evaluation",
  2222.   DET853 Invalid block address",
  2223.   DET854 Storage chain damaged",
  2224.   DET855 Invalid value for NUMERIC DIGITS %d",
  2225.   DET856 Invalid value for NUMERIC FUZZ %d",
  2226.   DET857 Invalid expression for NUMERIC FORM %s",
  2227. * DET998 Can't uninstall resident version
  2228. * DET999 Resident version does not support uninstall
  2229.  
  2230.  
  2231.  
  2232.  
  2233. Appendix K. Error messages                                             79
  2234.